/***********************************************************************
filename:   hgeImageManager.cpp
created:    Sun Jul 19 2009
author:     Paul D Turner <paul@cegui.org.uk>
*************************************************************************/
#include "hgeImageManager.h"
#include "hgeExceptions.h"
#include "hgeLogger.h"
#include "hgeGuiSystem.h"

//----------------------------------------------------------------------------//
// singleton instance pointer
template<> ImageManager* Singleton<ImageManager>::ms_Singleton = 0;

//----------------------------------------------------------------------------//
ImageManager::ImageManager()
{
	char addr_buff[32];
	sprintf(addr_buff, "(%p)", static_cast<void*>(this));
	hgeLogger::getSingleton().logEvent(
		"ImageManager singleton created. " + String(addr_buff));
}

//----------------------------------------------------------------------------//
ImageManager::~ImageManager()
{
	hgeLogger::getSingleton().logEvent(
		"---- Begining cleanup of Image system ----");

	while (!d_images.empty())
		destroyImage(d_images.begin());

	char addr_buff[32];
	sprintf(addr_buff, "(%p)", static_cast<void*>(this));
	hgeLogger::getSingleton().logEvent(
		"ImageManager singleton destroyed. " + String(addr_buff));
}

//----------------------------------------------------------------------------//
Image& ImageManager::createImage(const String& image_name, Texture& tex, const hgeRect& area, const Point& offset)
{
	hgeLogger::getSingleton().logEvent("Attempting to create Image '" +	image_name + "'.");

	ImageRegistry::const_iterator i(d_images.find(image_name));

	if (i != d_images.end())
		return getImage(image_name);

	// create new object ahead of time
	Image* object = new Image(tex, image_name, area, offset);

	d_images[image_name] = object;

	// return appropriate object instance (deleting any not required)
	return *object;
}

//----------------------------------------------------------------------------//
Image& ImageManager::createImageFromFile(const String& image_name, const String& filename)
{
	hgeLogger::getSingleton().logEvent("Attempting to create Image '" +
		image_name + "' using file '" + filename + "'.");

	ImageRegistry::const_iterator i(d_images.find(image_name));

	if (i != d_images.end())
		return getImage(image_name);

	// create new object ahead of time
	Image* object = new Image(filename, image_name);

	d_images[image_name] = object;

	// return appropriate object instance (deleting any not required)
	return *object;
}

Image& ImageManager::getImage(const String& object_name) const
{
	ImageRegistry::const_iterator i(d_images.find(object_name));

	if (i == d_images.end())
		throw UnknownObjectException("ImageManager::getImage: "
		"No object of named '" + object_name + "' is present in the collection.");

	return *i->second;
}

void ImageManager::destroyImage(ImageRegistry::iterator ob)
{
	char addr_buff[32];
	sprintf(addr_buff, "(%p)", static_cast<void*>(ob->second));
	hgeLogger::getSingleton().logEvent("Image named '" + ob->first + "' has been destroyed. " +
		addr_buff, Informative);

	delete ob->second;
	d_images.erase(ob);
}

//----------------------------------------------------------------------------//
void ImageManager::notifyDisplaySizeChanged(const Size& size)
{
	// notify all attached Image objects of the change in resolution
	ImageRegistry::iterator pos = d_images.begin(), end = d_images.end();

	/*for (; pos != end; ++pos)
	pos->second->notifyDisplaySizeChanged(size);*/
}

//----------------------------------------------------------------------------//
ImageManager::ImageIterator ImageManager::getImageIterator(void) const
{
	return ImageIterator(d_images.begin(), d_images.end());
}